home *** CD-ROM | disk | FTP | other *** search
/ EnigmA Amiga Run 1996 March / EnigmA AMIGA RUN 05 (1996)(G.R. Edizioni)(IT)[!][issue 1996-03][Skylink CD IV].iso / earcd / comm2 / parnet.lha / parnet / sources / unit_str.c < prev    next >
C/C++ Source or Header  |  1993-11-09  |  4KB  |  188 lines

  1.  
  2. /*
  3.  *  UNIT_STR.C            STREAM PROTOCOL (not impl yet)
  4.  *
  5.  *                currently just datagram proto.
  6.  */
  7.  
  8. #include "defs.h"
  9.  
  10. void StreamBeginIO(Iob *);
  11. void StreamAbortIO(Iob *);
  12. void StreamClose(Iob *);
  13. void StreamData(int, Packet *, long);
  14.  
  15. void UnitStreamOpen(Iob *, long, long);
  16.  
  17. /*
  18.  *  Called under Forbid
  19.  */
  20.  
  21. void
  22. UnitStreamOpen(iob, unitnum, flags)
  23. Iob *iob;
  24. long unitnum;
  25. long flags;
  26. {
  27.     Unit *unit;
  28.  
  29.     if (unit = FindUnitForPort(iob->io_Port)) {
  30.     if (unit->BeginIO != StreamBeginIO) {
  31.         iob->io_Error = PPERR_PORT_IN_USE;
  32.         return;
  33.     }
  34.     } else {
  35.     unit = AllocUnit(iob, StreamBeginIO, StreamAbortIO, StreamData, StreamClose);
  36.     }
  37.     iob->io_Unit = unit;
  38.     ++unit->RefCnt;
  39. }
  40.  
  41.  
  42. void
  43. StreamClose(iob)
  44. Iob *iob;
  45. {
  46.     Unit *unit = iob->io_Unit;
  47.  
  48.     if (--unit->RefCnt == 0) {
  49.     FreeUnit(unit);
  50.     }
  51.     iob->io_Unit = NULL;
  52. }
  53.  
  54. /*
  55.  *  UnitStreamData() is called whenever a low level network operation
  56.  *            completes for the given unit.  cmd is:
  57.  *
  58.  *            'r'     received data packet
  59.  *            'w'     wrote data packet
  60.  *            'W'     timeout writing data packet
  61.  *
  62.  *            The routine is called with the unit locked.
  63.  */
  64.  
  65. void
  66. StreamData(cmd, packet, actual)
  67. int cmd;
  68. Packet *packet;
  69. long actual;    /*  'w', 'W'    */
  70. {
  71.     Unit *unit = packet->io_Unit;
  72.     Iob *iob = packet->iob;        /*    NULL for 'r'    */
  73.     long n;
  74.  
  75.     switch(cmd) {
  76.     case 'r':
  77. #ifdef DEBUG
  78.     sprintf(StickyPort->DebugBuf, " RDSTR %d",actual);
  79. #endif
  80.  
  81.     if (iob = (Iob *)RemHead(&unit->PendIOR)) {
  82.         iob->io_Flags &= ~IOF_QUEUED;
  83.  
  84.         n = actual;
  85.         iob->io_Actual = actual;
  86.         if (n < 0)
  87.         n = 0;
  88.         if (n > iob->io_Length) {
  89.         n = iob->io_Length;
  90.         iob->io_Error = PPERR_WARN_OVFLOW;
  91.         }
  92.         movmem((char *)packet->Data1, (char *)iob->io_Data, n);
  93.         if ((iob->io_Flags & IOF_QUICK) == 0)
  94.         ReplyMsg(&iob->io_Message);
  95.     }
  96.  
  97.     /*
  98.      *  Note that if no read requests are pending the datagram is
  99.      *  thrown away.
  100.      */
  101.  
  102.     FreeParPacket(packet);
  103.     break;
  104.     case 'W':
  105. #ifdef DEBUG
  106.     sprintf(StickyPort->DebugBuf, " TMSTR %d",actual);
  107. #endif
  108.  
  109.     Remove(iob);
  110.     iob->io_Flags &= ~IOF_QUEUED;
  111.     iob->io_Error = 1;
  112.     iob->io_Actual = actual;
  113.     if ((iob->io_Flags & IOF_QUICK) == 0)
  114.         ReplyMsg(&iob->io_Message);
  115.     FreeParPacket(packet);
  116.     break;
  117.     case 'w':
  118. #ifdef DEBUG
  119.     sprintf(StickyPort->DebugBuf, " WRSTR %d",actual);
  120. #endif
  121.  
  122.     Remove(iob);
  123.     iob->io_Flags &= ~IOF_QUEUED;
  124.     iob->io_Actual = actual;
  125.     if ((iob->io_Flags & IOF_QUICK) == 0)
  126.         ReplyMsg(&iob->io_Message);
  127.     FreeParPacket(packet);
  128.     break;
  129.     }
  130. }
  131.  
  132. void
  133. StreamBeginIO(iob)
  134. Iob *iob;
  135. {
  136.     Unit *unit = iob->io_Unit;
  137.     Packet *packet;
  138.  
  139.     iob->io_Error = 0;
  140.     iob->io_Actual = 0;
  141.     iob->io_Message.mn_Node.ln_Type = NT_MESSAGE;
  142.  
  143.     switch(iob->io_Command) {
  144.     case CMD_READ:
  145.     LockAddr(unit->UnitLock);
  146.     iob->io_Flags &= ~IOF_QUICK;
  147.     iob->io_Flags |= IOF_QUEUED;
  148.     AddTail(&unit->PendIOR, iob);
  149.     UnlockAddr(unit->UnitLock);
  150.     return;
  151.     case CMD_WRITE:
  152.     packet = AllocParPacket(iob, unit, iob->io_Data, iob->io_Length, NULL, 0);
  153.     LockAddr(unit->UnitLock);
  154.     AddTail(&unit->PendIOW, iob);
  155.     UnlockAddr(unit->UnitLock);
  156.  
  157.     QueuePacketForWrite(packet);
  158.     return;
  159.     default:
  160.     CtlBeginIO(iob);
  161.     return;
  162.     }
  163. }
  164.  
  165. /*
  166.  *  Abort a read or write request.  Currently only read requests may be
  167.  *  aborted.
  168.  */
  169.  
  170. void
  171. StreamAbortIO(iob)
  172. Iob *iob;
  173. {
  174.     if (iob->io_Command == CMD_READ) {
  175.     LockAddr(iob->io_Unit->UnitLock);
  176.     if ((iob->io_Flags & (IOF_QUEUED|IOF_RUN)) == IOF_QUEUED) {
  177.         Remove(iob);
  178.         UnlockAddr(iob->io_Unit->UnitLock);
  179.         iob->io_Flags &= ~IOF_QUEUED;
  180.         iob->io_Error = -1;     /*    ??? */
  181.         ReplyMsg(&iob->io_Message);
  182.     } else {
  183.         UnlockAddr(iob->io_Unit->UnitLock);
  184.     }
  185.     }
  186. }
  187.  
  188.